package com.xiguanlezz.cn.client.naming.remote.grpc.redo.data;

import lombok.Getter;
import lombok.Setter;

/**
 * @Author：习惯了种种
 * @CreateDate：2024/11/25 14:40
 * @Description：重试实体类
 */
@Getter
public abstract class RedoData<T> {
    protected String serviceName;
    protected String groupName;

    // true表示本次是服务注册/订阅服务实例，false表示本次是服务注销/取消订阅服务实例
    @Setter
    @Getter
    private volatile boolean expectedRegistered;

    @Setter
    @Getter
    private volatile boolean registered; /* 服务注册/订阅服务实例时使用 */
    @Setter
    @Getter
    private volatile boolean unregistering; /* 服务注销/取消订阅服务实例时使用 */
    @Setter
    @Getter
    private T data;

    protected RedoData(String serviceName, String groupName) {
        this(serviceName, groupName, true);
    }

    protected RedoData(String serviceName, String groupName, boolean expectedRegistered) {
        this.serviceName = serviceName;
        this.groupName = groupName;
        this.expectedRegistered = expectedRegistered;
    }

    /**
     * 设置为已注册状态
     */
    public void registered() {
        this.registered = true;
        this.unregistering = false;
    }

    /**
     * 设置为已注销状态
     */
    public void unregistered() {
        this.registered = false;
        this.unregistering = true;
    }


    public boolean isNeedRedo() {
        return !RedoType.NONE.equals(getRedoType());
    }

    public RedoType getRedoType() {

        if (isRegistered() && !isUnregistering()) {

            return expectedRegistered ? RedoType.NONE : RedoType.UNREGISTER;

        } else if (isRegistered() && isUnregistering()) {

            return RedoType.UNREGISTER;

        } else if (!isRegistered() && !isUnregistering()) {

            return RedoType.REGISTER;

        } else {

            return expectedRegistered ? RedoType.REGISTER : RedoType.REMOVE;
        }
    }

    public enum RedoType {
        // 需要进行注册操作
        REGISTER,
        // 需要执行注销操作
        UNREGISTER,
        // 不执行任何操作
        NONE,
        // 从map中移除重做对象
        REMOVE;
    }

}
